package com.fh.modules.oms.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.fh.common.exception.Assert;
import com.fh.common.util.DateUtils;
import com.fh.common.util.UUIDGeneratorUtils;
import com.fh.common.web.impl.AbstractServiceImpl;
import com.fh.modules.ems.service.IEmsCouponService;
import com.fh.modules.oms.*;
import com.fh.modules.oms.entity.OmsOrderWechat;
import com.fh.modules.oms.entity.OmsOrderWechatItem;
import com.fh.modules.oms.mapper.OmsOrderWechatMapper;
import com.fh.modules.oms.model.OrderModel;
import com.fh.modules.oms.service.IOmsOrderWechatHistoryService;
import com.fh.modules.oms.service.IOmsOrderWechatItemService;
import com.fh.modules.oms.service.IOmsOrderWechatService;
import com.fh.modules.oms.service.IOmsShoppingCarService;
import com.fh.modules.oms.vo.OrderVo;
import com.fh.modules.pms.service.IPmsProductService;
import com.fh.modules.ums.entity.UmsMemberPartnerInfo;
import com.fh.modules.ums.entity.UmsMemberReceiveAddress;
import com.fh.modules.ums.model.MemberModel;
import com.fh.modules.ums.service.IUmsMemberReceiveAddressService;
import com.fh.modules.ums.service.IUmsMemberService;
import com.fhMall.request.SubmitOrderRequest;
import com.fhMall.response.SubmitOrderResponse;
import com.github.pagehelper.PageHelper;
import org.apache.commons.lang3.math.NumberUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.io.Serializable;
import java.math.BigDecimal;
import java.util.Date;
import java.util.List;

/**
 * @Description: 微信订单表
 * @author： code generator
 * @date： 2019-10-07
 * @version： V1.0
 */
@Service
public class OmsOrderWechatServiceImpl extends AbstractServiceImpl<OmsOrderWechatMapper, OmsOrderWechat> implements IOmsOrderWechatService {

    @Autowired
    private OmsOrderWechatMapper omsOrderWechatMapper;
    @Autowired
    private IOmsOrderWechatItemService omsOrderWechatItemService;
    @Autowired
    private IOmsShoppingCarService omsShoppingCarService;
    @Autowired
    private IOmsOrderWechatHistoryService omsOrderWechatHistoryService;
    @Autowired
    private IUmsMemberReceiveAddressService umsMemberReceiveAddressService;
    @Autowired
    private IEmsCouponService emsCouponService;
    @Autowired
    private IUmsMemberService umsMemberService;
    @Autowired
    private IPmsProductService pmsProductService;

    @Override
    public List<OrderModel> queryOrder(OrderVo orderVo) {
        PageHelper.startPage(orderVo.getPageNo(), orderVo.getPageSize(), false);
        return omsOrderWechatMapper.queryOrder(orderVo);
    }
    @Override
    public void deleteEntityByDelFlag(Serializable id){
        OmsOrderWechat omsOrderWechat=this.getById(id);
        Assert.isFalse(omsOrderWechat.getStatus()==0,"只有已取消订单能删除");
        super.deleteEntityByDelFlag(id);
    }

    @Override
    public Integer countOrderByStatusAndMember(Integer memberId,Integer status){
        LambdaQueryWrapper<OmsOrderWechat> query=new LambdaQueryWrapper<>();
        query.eq(OmsOrderWechat::getMemberId,memberId);
        query.eq(OmsOrderWechat::getDelFlag,0);
        query.eq(OmsOrderWechat::getStatus,status);
        return this.count(query);
    }
    @Override
    @Transactional
    public SubmitOrderResponse payAgain(Integer orderId,Integer memberId){
        OmsOrderWechat omsOrderWechat=this.getById(orderId);
        Assert.isFalse(omsOrderWechat.getMemberId().intValue()==memberId,"订单不属于付款用户");
        omsOrderWechat.setWechatPrepayId(UUIDGeneratorUtils.getCode());
        this.updateById(omsOrderWechat);
        return SubmitOrderResponse.builder().orderId(omsOrderWechat.getId())
                .wechatPrepayId(omsOrderWechat.getWechatPrepayId())
                .payPrice(omsOrderWechat.getPayPrice()).build();
    }

    @Override
    @Transactional
    public SubmitOrderResponse order(SubmitOrderRequest submitOrderRequest) {
        //1.生成OmsOrderWechat，冻结优惠券，冻结积分
        OmsOrderWechat omsOrderWechat = this.saveOmsOrderWechat(submitOrderRequest);
        emsCouponService.useCoupon(omsOrderWechat);
        //TODO 冻结积分
        //2.生成OmsOrderWechatItem 列表
        omsOrderWechatItemService.addOrderItems(omsOrderWechat, submitOrderRequest);
        //3.生成OmsOrderWechatHistory 历史记录
        omsOrderWechatHistoryService.saveWechatHistory(omsOrderWechat, OrderOperateMan.MEMBER, OrderNote.ORDER, OrderStatus.NOT_PAY);
        //4.如果是购物车下单，删掉购物车商品
        omsShoppingCarService.deleteBatchEntityByDelFlag(submitOrderRequest.getShoppingCarIds());
        return SubmitOrderResponse.builder().orderId(omsOrderWechat.getId())
                .wechatPrepayId(omsOrderWechat.getWechatPrepayId())
                .payPrice(omsOrderWechat.getPayPrice()).build();
    }

    @Override
    public boolean cancelOrder(Integer orderId) {
        return cancelOrder(super.getById(orderId));
    }

    @Override
    public boolean cancelOrder(OmsOrderWechat omsOrderWechat) {
        Assert.isTrue(omsOrderWechat == null, "订单不存在");
        //1、修改订单状态
        changeOrderStatus(omsOrderWechat, OrderStatus.CANCELLED);
        //2、增加订单变更历史记录
        omsOrderWechatHistoryService.saveWechatHistory(omsOrderWechat, OrderOperateMan.MEMBER, OrderNote.ORDER, OrderStatus.NOT_PAY);
        //3、返还优惠券
        Integer couponId = omsOrderWechat.getCouponId();
        if (couponId != null) {
            emsCouponService.returnCoupon(omsOrderWechat.getCouponId());
        }
        //TODO 4、返回积分

        return false;
    }

    /**
     * 保存订单基本信息
     *
     * @param submitOrderRequest
     * @return
     */
    private OmsOrderWechat saveOmsOrderWechat(SubmitOrderRequest submitOrderRequest) {
        int notPayOrderCount=this.countOrderByStatusAndMember(submitOrderRequest.getMemberId(),OrderStatus.NOT_PAY.getValue());
        List imtes = submitOrderRequest.getOrderItem();
        Assert.isTrue(notPayOrderCount>0,"您还有未支付订单");
        Assert.isTrue(imtes == null || imtes.size() == 0, "没有下单商品");
        Assert.isTrue(submitOrderRequest.getMemberReceiveAddress() == null, "请填写收货地址");
        OmsOrderWechat omsOrderWechat = new OmsOrderWechat();
        BeanUtils.copyProperties(submitOrderRequest, omsOrderWechat);
        omsOrderWechat.setIntegrationPrice(new BigDecimal(omsOrderWechat.getIntegration()==null?0:omsOrderWechat.getIntegration()));
        omsOrderWechat.setPromotionPrice(new BigDecimal(0));
        UmsMemberReceiveAddress umsMemberReceiveAddress = umsMemberReceiveAddressService.getById(submitOrderRequest.getMemberReceiveAddress());
        OrderUtils.initOrderInfo(omsOrderWechat, umsMemberReceiveAddress);
        omsOrderWechat.setItemCount(imtes.size());
        omsOrderWechat.setOrderSn(DateUtils.getSnPre()+UUIDGeneratorUtils.getRandomNumberCode(6));
        omsOrderWechat.setWechatPrepayId(UUIDGeneratorUtils.getCode());
        this.save(omsOrderWechat);
        return omsOrderWechat;
    }


    /**
     * 改变订单状态
     *
     * @param orderId
     * @param targetStatus 目标状态
     * @throws OrderStatusChangeException
     */
    public void changeOrderStatus(Integer orderId, OrderStatus targetStatus) {
        changeOrderStatus(this.getById(orderId), targetStatus);
    }


    public void changeOrderStatus(OmsOrderWechat omsOrderWechat, OrderStatus targetStatus) {
        int status = omsOrderWechat.getStatus();
        OrderStatusValidator validator = new OrderStatusValidator(status, targetStatus);
        validator.validate();
        omsOrderWechat.setStatus(targetStatus.getValue());
        omsOrderWechat.setModifyTime(new Date());
        super.updateById(omsOrderWechat);
    }

    @Override
    public void confirmRecieve(Integer orderId, Integer memberId) {
        OmsOrderWechat omsOrderWechat = this.getById(orderId);
        Assert.isFalse(memberId.intValue() == omsOrderWechat.getMemberId(), "会员信息错误，拒绝操作");
        omsOrderWechat.setConfirmStatus(1);
        omsOrderWechat.setReceiveTime(new Date());
        changeOrderStatus(omsOrderWechat, OrderStatus.FINISHED);
    }

    @Override
    @Transactional
    public void paySuccess(String outTradeNo, String transactionId) {
        String wechatPrepayId = outTradeNo;
        OmsOrderWechat omsOrderWechat = this.getOne(new LambdaQueryWrapper<OmsOrderWechat>().eq(OmsOrderWechat::getWechatPrepayId, wechatPrepayId));

        omsOrderWechat.setTransactionId(transactionId);
        omsOrderWechat.setPaymentTime(new Date());
        changeOrderStatus(omsOrderWechat, OrderStatus.PAY_SUCCESS);

        MemberModel memberInfo =umsMemberService.getMemberInfo(omsOrderWechat.getMemberId());
        int parnterType=memberInfo.getMemberInfo().getPartnerType();
        //积分,实际支付价格-运费
        BigDecimal payPrice=omsOrderWechat.getPayPrice();
        BigDecimal productMoney=payPrice.subtract(omsOrderWechat.getFreightPrice());
        int integration=productMoney.intValue();
        if(parnterType!=1){
            //购买人是非合伙人只增加积分和消费额
            umsMemberService.addMemberConsumptionInformation(integration,payPrice,memberInfo.getMemberInfo());
            //如果购买人有上级合伙人则增加合伙人团队提成信息
            if(memberInfo.getPartnerInfo()!=null&&memberInfo.getPartnerInfo().getOwnPartnerInfo()!=null){
                UmsMemberPartnerInfo umsMemberPartnerInfo=memberInfo.getPartnerInfo().getOwnPartnerInfo();
                umsMemberService.addParnterTeamSale(this.calculateTeamCommission(omsOrderWechat,umsMemberPartnerInfo),productMoney,
                        umsMemberPartnerInfo);
            }
        }else{
            //购买人是合伙人增加总消费额
            umsMemberService.addMemberConsumptionInformation(0,payPrice,memberInfo.getMemberInfo());
            //购买人是合伙人增加合伙人团队提成信息
            UmsMemberPartnerInfo umsMemberPartnerInfo=umsMemberService.getPartnerInfo(omsOrderWechat.getMemberId());
            umsMemberService.addParnterTeamSale(this.calculateTeamCommission(omsOrderWechat,umsMemberPartnerInfo),productMoney,
                    umsMemberPartnerInfo);
        }

    }

    /**
     * 计算销售提成
     * @return
     */
    private BigDecimal calculateTeamCommission(OmsOrderWechat omsOrderWechat,UmsMemberPartnerInfo umsMemberPartnerInfo){
        List<OmsOrderWechatItem> items=omsOrderWechatItemService.getOrderItem(omsOrderWechat.getId());
        BigDecimal total=new BigDecimal(0);
        //最后需要扣除的比例，优惠券等优惠金额*这个折扣
        int percent=0;
        for (OmsOrderWechatItem item : items) {
            int salePercentage= pmsProductService.getSalePercentage(item.getProductId(),umsMemberPartnerInfo.getMemberLevelId());
            BigDecimal money= item.getProductPrice().multiply(new BigDecimal(salePercentage)).divide(new BigDecimal(100));
            total=total.add(money);
            if(salePercentage>percent){
                percent=salePercentage;
            }
        }
        BigDecimal discount=omsOrderWechat.getCouponPrice().add(omsOrderWechat.getIntegrationPrice()).add(omsOrderWechat.getPromotionPrice());
        return total.subtract(discount.multiply(new BigDecimal(percent)).divide(new BigDecimal(100)));
    }

}
